#include "ws2812_driver.h"
#include <stdio.h>

// color 转 buff
// 发送顺序 GRB
uint8_t buff_trans(uint8_t num, rgb_t *leds, ws2812_driver_t *buff)
{
    if (buff->buff_len - buff->reset_len < num * 24)
        return 1;

    for (uint8_t i = 0; i < num; i++)
    {
        for (uint8_t j = 0; j < 8; j++)
        {
            buff->buff[i * 24 + j] = (leds[i].g & (0x80 >> j)) ? WS2812_CODE_ONE_DUTY : WS2812_CODE_ZERO_DUTY;
            buff->buff[i * 24 + 8 + j] = (leds[i].r & (0x80 >> j)) ? WS2812_CODE_ONE_DUTY : WS2812_CODE_ZERO_DUTY;
            buff->buff[i * 24 + 16 + j] = (leds[i].b & (0x80 >> j)) ? WS2812_CODE_ONE_DUTY : WS2812_CODE_ZERO_DUTY;
        }
    }
    return 0;
}

static uint16_t buff_aar1[WS2812_1_NUM * 24 + 100] = {0};
ws2812_driver_t buff_1 = {
    .buff_len = WS2812_1_NUM * 24 + 100,
    .reset_len = 100,
    .buff = buff_aar1};

static uint16_t buff_aar2[WS2812_2_NUM * 24 + 100] = {0};
ws2812_driver_t buff_2 = {
    .buff_len = WS2812_2_NUM * 24 + 100,
    .reset_len = 100,
    .buff = buff_aar2};

static uint16_t buff_aar3[WS2812_3_NUM * 24 + 100] = {0};
ws2812_driver_t buff_3 = {
    .buff_len = WS2812_3_NUM * 24 + 100,
    .reset_len = 100,
    .buff = buff_aar3};

uint8_t buff_send_1(uint8_t num, rgb_t *leds)
{
    buff_trans(num, leds, &buff_1);
    // for (uint16_t i = 0; i < num * 24; i++)
    // {
    //     printf("%u\n", buff_1.buff[i]);
    // }
    HAL_TIM_PWM_Start_DMA(&htim3, TIM_CHANNEL_1, (uint32_t *)(buff_1.buff), buff_1.buff_len);
    return 0;
}

uint8_t buff_send_2(uint8_t num, rgb_t *leds)
{
    buff_trans(num, leds, &buff_2);
    // for (uint16_t i = 0; i < num * 24; i++)
    // {
    //     printf("%u\n", buff_2.buff[i]);
    // }
    HAL_TIM_PWM_Start_DMA(&htim3, TIM_CHANNEL_4, (uint32_t *)(buff_2.buff), buff_2.buff_len);
    return 0;
}

uint8_t buff_send_3(uint8_t num, rgb_t *leds)
{
    buff_trans(num, leds, &buff_3);
    // for (uint16_t i = 0; i < num * 24; i++)
    // {
    //     printf("%u\n", buff_3.buff[i]);
    // }
    HAL_TIM_PWM_Start_DMA(&htim1, TIM_CHANNEL_4, (uint32_t *)(buff_3.buff), buff_3.buff_len);
    return 0;
}

void HAL_TIM_PWM_PulseFinishedCallback(TIM_HandleTypeDef *htim)
{
    if (htim->Instance == TIM1)
    {
        if (htim->Channel == HAL_TIM_ACTIVE_CHANNEL_4)
            HAL_TIM_PWM_Stop_DMA(&htim1, TIM_CHANNEL_4);
    }
    if (htim->Instance == TIM3)
    {
        if (htim->Channel == HAL_TIM_ACTIVE_CHANNEL_1)
            HAL_TIM_PWM_Stop_DMA(&htim3, TIM_CHANNEL_1);
        if (htim->Channel == HAL_TIM_ACTIVE_CHANNEL_4)
            HAL_TIM_PWM_Stop(&htim3, TIM_CHANNEL_4);
    }
    
}
